package com.aigc.sclassroom.service.impl;

import com.aigc.sclassroom.mapper.SignMapper;
import com.aigc.sclassroom.mapper.SignRecordMapper;
import com.aigc.sclassroom.mapper.TeamMapper;
import com.aigc.sclassroom.pojo.Sign;
import com.aigc.sclassroom.pojo.SignRecord;
import com.aigc.sclassroom.service.SignService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.messaging.simp.SimpMessagingTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;
import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.stream.Collectors;


@Service
public class SignServiceImpl implements SignService {

    @Autowired
    private SignMapper signMapper;

    @Autowired
    private SignRecordMapper recordMapper;

    @Autowired
    private TeamMapper teamMapper; // 假设TeamMapper已存在

    @Autowired
    private SimpMessagingTemplate messagingTemplate;

 /*   public SignServiceImpl(SignRecordMapper recordMapper) {
        this.recordMapper = recordMapper;
    }*/

    @Override
    // 教师发起签到
    @Transactional
    public Sign createSign(Long classId, Integer duration) {
        // 检查是否存在重复的签到记录
        Integer count =signMapper.selectCountByClassId(classId);
        if (count>=4) {
            throw new RuntimeException("每节课最多签到三次");
        }
        Sign sign = new Sign();
        sign.setClassId(classId);
        sign.setSignCode(generateRandomCode());
        sign.setStartTime(LocalDateTime.now());
        sign.setEndTime(LocalDateTime.now().plusMinutes(duration));
        sign.setDuration(duration);
        signMapper.insertSign(sign);
        return sign;
    }
    /**
     * 学生签到方法
     *
     * @param signId 签到活动的ID
     * @param userId 学生的用户ID
     * @param code   签到验证码
     * @throws RuntimeException 当签到不存在、签到码错误、签到已结束或学生已签到时会抛出此异常
     */

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void studentSign(Long signId, Long userId, String code) {
        try {
            Sign sign = signMapper.selectById(signId);
            if (sign == null) {
                throw new RuntimeException("签到不存在");
            }
            if (!sign.getSignCode().equals(code)) {
                throw new RuntimeException("签到码错误");
            }
            if (LocalDateTime.now().isAfter(sign.getEndTime())) {
                throw new RuntimeException("签到已结束");
            }
            // 检查该学生是否已经有签到记录
            Integer count = recordMapper.checkSigned(signId, userId);
            if (count > 0) {
                throw new RuntimeException("请勿重复签到");
            }
            // 创建新的签到记录
            SignRecord record = new SignRecord();
            record.setSignId(signId);
            record.setUserId(userId);
            record.setStatus(1);
            record.setSignTime(LocalDateTime.now());
            recordMapper.insertRecod(record);
            // 推送实时数据
            messagingTemplate.convertAndSend("/topic/sign/" + signId, getSignStatus(signId));
        } catch (Exception e) {
            TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
            throw e;
        }
    }

    // 生成6位随机码
    private String generateRandomCode() {
        return String.format("%06d", new Random().nextInt(999999));
    }
    /**
     * 获取签到状态
     *
     * @param signId 签到ID
     * @return 包含签到状态的Map对象，包含已签到人数、总人数以及每个学生的签到状态
     */
    @Override
    public Map<String, Object> getSignStatus(Long signId) {
        List<SignRecord> records = recordMapper.selectBySignId(signId);
        long signedCount = records.stream().filter(r -> r.getStatus() == 1).count();
        return Map.of(
                "signed", signedCount,
                "total", records.size(),
                "students", records.stream().map(r -> Map.of(
                        "userId", r.getUserId(),
                        "status", r.getStatus()
                )).collect(Collectors.toList())
        );
    }

}